package com.hundsun.epay.autosimu.internal.rules;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

import com.hundsun.epay.autosimu.utils.StringUtility;

/**
 * 字段规则
 * @author Clown
 *
 */
public abstract class Rules {
	public static final String DEFAULT_MAPPING_KEY = "";
	
	protected String name;
	private Rules parent;
	private boolean isRepeat;
	private boolean inArray;
	private int index;
	private boolean isRoot;
	
	/**
	 * 递归解析规则
	 * @param rules
	 */
	protected final void parseRules(String rules){
		if(rules.endsWith("#")){
			throw new RuntimeException("A rule defination can't end with '#'");
		}
		int childSign = rules.lastIndexOf("#");
		if(childSign < 0){   //-1
			this.parent = null;
		}else if(childSign == 0){   //最后一个#处于最开始位置
			this.parent = null;
			this.isRoot = true;
		}else{
			Rules parent = getParentInstance();
			parent.parseRules(rules.substring(0, childSign));
			this.parent = parent;
		}
		parseRulesInternal(rules.substring(childSign + 1));   //-1 + 1 = 0
	}
	
	private void parseRulesInternal(String rules){
		//检查字段规则，只允许一个'[' 一个']',这两个字符中间只允许数字出现，或为空,且 数组标识只允许出现在结尾处
		int countLeft = StringUtility.countByFinder("\\[", rules);
		int countRight = StringUtility.countByFinder("\\]", rules);
		if(countLeft > 1 || countRight > 1 || countLeft != countRight){
			throw new RuntimeException("Invalid rule defination, Please check the character '[' and ']' happend count");
		}
		this.inArray = false;
		if(rules.endsWith("]")){
			if(!checkIsArray(rules)){
				throw new RuntimeException("Invalid rule defination for one array key");
			}
			this.inArray = true;
			if(rules.endsWith("[]")){
				this.isRepeat = true;
			}else{
				int index = Integer.parseInt(rules.substring(rules.indexOf("[") + 1, rules.indexOf("]")));
				this.index = index;
				this.isRepeat = false;
			}
			rules = rules.substring(0, rules.indexOf("["));
		}
		this.name = rules;
	}
	
	private static boolean checkIsArray(String rules){
		String regex = "\\[\\d*\\]$";
		Pattern pattern = Pattern.compile(regex);
		Matcher matcher = pattern.matcher(rules);
		return matcher.find();
//		return Pattern.matches(regex, rules);
	}
	
	public static void main(String[] args) {
		System.out.println(checkIsArray("details#date[0]"));;
	}
	
	/**
	 * 获取父规则实例
	 * @return
	 */
	protected abstract Rules getParentInstance();

	/**
	 * @return the name
	 */
	public String getName() {
		return name;
	}

	/**
	 * @return the parent
	 */
	public Rules getParent() {
		return parent;
	}

	/**
	 * @return the isRepeat
	 */
	public boolean isRepeat() {
		return isRepeat;
	}

	/**
	 * @return the inArray
	 */
	public boolean isInArray() {
		return inArray;
	}

	/**
	 * @return the index
	 */
	public int getIndex() {
		return index;
	}

	/**
	 * @return the isRoot
	 */
	public boolean isRoot() {
		return isRoot;
	}
	
	
}
